home *** CD-ROM | disk | FTP | other *** search
/ The 640 MEG Shareware Studio 2 / The 640 Meg Shareware Studio CD-ROM Volume II (Data Express)(1993).ISO / clang / jcool01.zip / D_NODE.C < prev    next >
C/C++ Source or Header  |  1992-08-20  |  7KB  |  180 lines

  1. //
  2. // Copyright (C) 1991 Texas Instruments Incorporated.
  3. //
  4. // Permission is granted to any individual or institution to use, copy, modify,
  5. // and distribute this software, provided that this complete copyright and
  6. // permission notice is maintained, intact, in all copies and supporting
  7. // documentation.
  8. //
  9. // Texas Instruments Incorporated provides this software "as is" without
  10. // express or implied warranty.
  11. //
  12.  
  13. #include <cool/D_Node.h>
  14.  
  15. // compare_s -- Compare function for class
  16. template <class Type, int nchild> 
  17. //##CoolD_Node<Type,nchild>::Compare CoolD_Node<Type,nchild>::compare_s = &default_CoolD_Node_compare;
  18. Boolean (*CoolD_Node<Type,nchild>::compare_s)(const Type&, const Type&) = &default_CoolD_Node_compare;
  19.  
  20.  
  21. // CoolD_Node -- Simple constructor that allocates enough storage for a vector of
  22. //           pointers to CoolD_Node objects
  23. // Input:    None
  24. // Output:   None
  25.  
  26. template <class Type, int nchild> 
  27. CoolD_Node<Type,nchild>::CoolD_Node() {
  28.   sub_trees.set_alloc_size(nchild);        // fix growth ratio instead
  29.   for (int i = 0; i < nchild; i++)        // For each pointer in vector
  30.     this->sub_trees.push(NULL);            // Insure NULL pointer value
  31. }
  32.  
  33.  
  34. // CoolD_Node -- Simple constructor that allocates enough storage for a vector of
  35. //           pointers to CoolD_Node objects and assigns an initial data value
  36. // Input:    Data slot value
  37. // Output:   None
  38.  
  39. template <class Type, int nchild> 
  40. CoolD_Node<Type,nchild>::CoolD_Node(const Type& value) {
  41.   for (int i = 0; i < nchild; i++)        // For each pointer in vector
  42.     this->sub_trees.push(NULL);            // Insure NULL pointer value
  43.   this->set(value);                // Copy initial data value
  44. }
  45.  
  46.  
  47. // CoolD_Node -- Copy constructor makes deep copy
  48. // Input:    Reference to CoolD_Node
  49. // Output:   None
  50.  
  51. template <class Type, int nchild> 
  52. CoolD_Node<Type,nchild>::CoolD_Node(const CoolD_Node<Type,nchild>& n) {
  53.   for (int i = 0; i < n.sub_trees.length(); i++) // For each pointer in vector
  54.     this->sub_trees.push(copy_nodes(n.sub_trees[i])); // Deep copy of subnodes
  55.   this->set(n.get());                // Copy data value
  56.   this->compare_s = n.compare_s;        // Set compare method
  57. }
  58.  
  59.  
  60. // ~CoolD_Node -- Destructor for the CoolD_Node<Type,nchild> class
  61. // Input:     None
  62. // Output:    None
  63.  
  64. template <class Type, int nchild> 
  65. CoolD_Node<Type,nchild>::~CoolD_Node() {
  66.   for (int i = 0; i < this->num_subtrees(); i++) // For each pointer in vector
  67.     delete this->sub_trees[i];            // Invoke destructor
  68. }
  69.  
  70.  
  71. // is_leaf -- Determine if node has any children
  72. // Input:     None
  73. // Output:    TRUE if no children, else FALSE
  74.  
  75. template <class Type, int nchild> 
  76. Boolean CoolD_Node<Type,nchild>::is_leaf () const {
  77.   for (int i = 0; i < this->num_subtrees(); i++)
  78.     if (this->sub_trees[i])
  79.       return (FALSE);
  80.   return TRUE;
  81. }
  82.  
  83.  
  84. // operator= -- Overload the assignment operator to copy all values from one
  85. //              node object to another. This routine could potentially result
  86. //              in a complete deep copy, since for each valid sub_tree pointer,
  87. //              a new node is allocated and its sub_tree pointers copied.
  88. // Input:       Reference to CoolD_Node
  89. // Output:      Rererence to updated CoolD_Node
  90.  
  91. template <class Type, int nchild> 
  92. CoolD_Node<Type,nchild>& CoolD_Node<Type,nchild>::operator= (const CoolD_Node<Type,nchild>& n) {
  93.   int i;
  94.   for (i = 0; i < this->num_subtrees(); i++) // Recursively delete old tree
  95.     delete this->sub_trees.pop();         // and pop from vector
  96.   for (i = 0; i < n.num_subtrees(); i++)     // Push in new subtrees
  97.     this->sub_trees.push(copy_nodes(n.sub_trees[i]));
  98.   this->set(n.get());                // Copy data value
  99.   return *this;                    // Return reference
  100. }
  101.  
  102. // insert_before -- Insert sub-tree pointer to child before the specified
  103. //                  zero-relative sub-tree index (numbered from left to right)
  104. // Input:           Pointer to child node, zero-relative index
  105. // Output:          TRUE/FALSE
  106.  
  107. template <class Type, int nchild> 
  108. Boolean CoolD_Node<Type,nchild>::insert_before (CoolD_Node<Type,nchild>& n, int index) {
  109. #if ERROR_CHECKING
  110.   if (index < 0) {                // If index out of range
  111.     this->index_error ("insert_before", index);    // Raise exception
  112.     return FALSE;                // Return failure status
  113.   }
  114. #endif
  115.   this->sub_trees.insert_before(&n, index);    // Pointer to new sub-tree
  116.   return TRUE;                    // Return success status
  117. }
  118.  
  119.  
  120. // insert_after -- Insert sub-tree pointer to child after the specified
  121. //                 zero-relative sub-tree index (numbered from left to right)
  122. // Input:          Pointer to child node, zero-relative index
  123. // Output:         TRUE/FALSE
  124.  
  125. template <class Type, int nchild> 
  126. Boolean CoolD_Node<Type,nchild>::insert_after (CoolD_Node<Type,nchild>& n, int index) {
  127. #if ERROR_CHECKING
  128.   if (index < 0) {                // If index out of range
  129.     this->index_error ("insert_after", index);    // Raise exception
  130.     return FALSE;                // Return failure status
  131.   }
  132. #endif
  133.   this->sub_trees.insert_after(&n, index);    // Pointer to new sub-tree
  134.   return TRUE;                    // Return success status
  135. }
  136.  
  137.  
  138. // copy_nodes -- Copies this node and all its subnodes
  139. // Input:       pointer to node to be copied
  140. // Output:      pointer to new copy of node with all new subnodes.
  141.  
  142. template <class Type, int nchild>
  143. CoolD_Node<Type,nchild>* CoolD_Node<Type,nchild>::copy_nodes (const CoolD_Node<Type,nchild>* n) const {
  144.   if (n == NULL)                
  145.     return NULL;
  146.   CoolD_Node<Type,nchild>* new_n = new CoolD_Node<Type,nchild>; 
  147.   for (int i = 0; i < n->num_subtrees(); i++)    // For each pointer in vector
  148.     new_n->sub_trees.push(copy_nodes(n->sub_trees[i])); // Deep copy of subnodes
  149.   new_n->data = n->data;                   // Copy data value
  150.   return new_n;                      // Return copied node.
  151. }
  152.  
  153.  
  154. // index_error -- Raise exception for invalid index
  155. // Input:         Function name, invalid index
  156. // Output:        None
  157.  
  158. template <class Type, int nchild> 
  159. void CoolD_Node<Type,nchild>::index_error (const char* fcn, int n) {
  160.   //RAISE Error, SYM(CoolD_Node), SYM(Out_Of_Range),
  161.   printf ("CoolD_Node<%s,%d>::%s: Index %d out of range.\n", "Type", nchild,
  162.       fcn, n);
  163.   abort ();
  164. }
  165.  
  166.  
  167. // default_CoolD_Node_compare -- Default node comparison function utilizing builtin
  168. //                           less than, equal, and greater than operators
  169. // Input:                    Reference to two Type data values
  170. // Output:                   -1, 0, or 1 if less than, equal to, or greater than
  171.  
  172. template <class Type>
  173. int default_CoolD_Node_compare (const Type& v1, const Type& v2) {
  174.     if (v1 == v2)                // If data items equal
  175.       return 0;                    // Return zero
  176.     if (v1 < v2)                // If this less than data
  177.       return -1;                // Return negative one
  178.     return 1;                    // Else return positive one
  179. }
  180.